/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package br.unicamp.ft.robustez;

import apps.Addresses;
import java.io.IOException;
import java.lang.management.ManagementFactory;
import java.nio.ByteBuffer;
import java.nio.channels.AsynchronousCloseException;
import javax.management.MBeanServer;
import javax.management.ObjectName;
import net.sf.neem.MulticastChannel;
import net.sf.neem.ProtocolMBean;

/**
 *
 * @author marcelo
 */
public class Communicator extends Thread {

    private FramePrincipal app;
    private MulticastChannel neem;

    public Communicator(FramePrincipal app) {
        this(app,"null");
    }
    
    public Communicator(FramePrincipal app,String remoteNode) {
        this.app = app;
        this.conecta(remoteNode);
        setDaemon(true);
        start();
    }

    public void run() {
        try {
            while (true) {
                byte[] buf = new byte[1000];
                ByteBuffer bb = ByteBuffer.wrap(buf);

                neem.read(bb);
                app.mostraLog("> " + new String(buf));
            }
        } catch (AsynchronousCloseException ace) {
            // Exiting.
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    public void sendMessage(String message) throws IOException {
        neem.write(ByteBuffer.wrap(message.getBytes()));
    }

    public void conecta(String remoteNode) {
        try {
            this.neem = new MulticastChannel(Addresses.parse(":", true));
            this.app.mostraLog("Started: " + neem.getLocalSocketAddress());
            if (neem.getLocalSocketAddress().getAddress().isLoopbackAddress()) {
                this.app.mostraLog("WARNING: Hostname resolves to loopback address! Please fix network configuration\nor expect only local peers to connect.");
            }

            MBeanServer mbs = ManagementFactory.getPlatformMBeanServer();
            ProtocolMBean mbean = neem.getProtocolMBean();
            ObjectName name = new ObjectName("net.sf.neem:type=Protocol,id=" + mbean.getLocalId());
            mbs.registerMBean(mbean, name);
            
            if (remoteNode != "null") {
                neem.connect(Addresses.parse(remoteNode, false));
            }
            
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    public void close() {
        this.neem.close();
    }
}
